/**
 * @file main.cpp
 * @brief 发布-订阅系统示例入口，演示订阅与发布的基本用法。
 */

#include "event_bus.h"

#include <iostream>
#include <thread>

int main() {
    using namespace std::chrono_literals;

    EventBus bus;

    // 注册主题 "alerts" 的订阅者。
    auto alerts_sub = bus.Subscribe("alerts", [](const Message& msg) {
        std::cout << "[alerts subscriber] received: "
                  << msg.payload << '\n';
    });

    // 注册主题 "metrics" 的订阅者。
    auto metrics_sub = bus.Subscribe("metrics", [](const Message& msg) {
        std::cout << "[metrics subscriber] received: "
                  << msg.payload << '\n';
    });

    // 同时监听多个主题，可重复订阅。
    auto all_alerts = bus.Subscribe("alerts", [](const Message& msg) {
        std::cout << "[all subscriber] alerts -> "
                  << msg.payload << '\n';
    });
    auto all_metrics = bus.Subscribe("metrics", [](const Message& msg) {
        std::cout << "[all subscriber] metrics -> "
                  << msg.payload << '\n';
    });

    // 模拟两个发布者线程分别向不同主题发布消息。
    std::thread publisherA([&bus] {
        for (int i = 1; i <= 3; ++i) {
            bus.Publish("alerts",
                        "disk space low: " + std::to_string(90 + i) + "%");
            std::this_thread::sleep_for(40ms);
        }
    });

    std::thread publisherB([&bus] {
        for (int i = 1; i <= 3; ++i) {
            bus.Publish("metrics",
                        "cpu load = " + std::to_string(i * 15) + "%");
            std::this_thread::sleep_for(60ms);
        }
    });

    publisherA.join();
    publisherB.join();

    // 等待消费者线程处理完最后一批消息。
    std::this_thread::sleep_for(100ms);

    std::cout << "Unsubscribing 'alerts' subscriber...\n";
    alerts_sub.Reset();  // 演示手动退订。

    // 再发布一条 "alerts"，只剩其他订阅者会收到。
    bus.Publish("alerts", "disk space recovered: 70%");
    std::this_thread::sleep_for(50ms);

    // 停止 EventBus，安全退出。
    bus.Stop();
    return 0;
}